﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.IO;
using System.Threading;

namespace USREOUCheck
{
    public partial class MainForm : Form
    {
        #region Private Members

        private int start = 0;
        private int indexOfSearchText = 0;

        enum SearchResultState
        { 
            All,
            Found,
            NotFound
        }

        #endregion Private Members

        #region Constructors

        public MainForm()
        {
            InitializeComponent();
        }

        #endregion Constructors

        #region Private Methods

        private void StartRequestInNewThread()
        {
            DateTime startTime = new DateTime();

            try
            {
                Classes.ServiceRequest.LoadCodesFromFile(openFileDialog.FileName);
                
                pBar.Visible = true;
                messageLabel.Visible = true;

                pBar.Minimum = 0;
                pBar.Maximum = Classes.ServiceRequest.Persons.Count;
                pBar.Value = 0;
                pBar.Step = 1;

                startTime = DateTime.Now;

                foreach (Classes.JuridicalPerson person in Classes.ServiceRequest.Persons)
                {
                    Stream request = Classes.ServiceRequest.SendRequest(person.EdrpouCode, true);
                    person.FullInfo = Classes.ServiceRequest.ParseRequestResult(request);

                    if (person.FullInfo.Contains("нічого не знайдено") || person.FullInfo.Contains("Невiрно"))
                        person.Founded = false;
                    else
                        person.Founded = true;

                    pBar.PerformStep();
                    timeLabel.Text = (DateTime.Now - startTime).ToString();
                    Application.DoEvents();
                }

                messageLabel.Visible = false;
                pBar.Visible = false;                
            }
                             
            catch (Exception ex)
            {
                MessageBox.Show("Произошла ошибка:\n" + ex.Message +
                                "\nВ методе: " + ex.TargetSite,
                                "Ошибка",
                                MessageBoxButtons.OK,
                                MessageBoxIcon.Error);
            }            
        }

        private int FindMyText(string txtToSearch, int searchStart, int searchEnd)
        {
            if (searchStart > 0 && searchEnd > 0 && indexOfSearchText >= 0)
            {
                resultRichTextBox.Undo();
            }

            int retVal = -1;

            if (searchStart >= 0 && indexOfSearchText >= 0)
            {
                if (searchEnd > searchStart || searchEnd == -1)
                {
                    indexOfSearchText = resultRichTextBox.Find(txtToSearch, searchStart, searchEnd, RichTextBoxFinds.None);

                    if (indexOfSearchText != -1)
                    {
                        retVal = indexOfSearchText;
                    }
                }
            }

            return retVal;
        }      

        private void AppendTo(bool? all, bool? founded, bool clear)
        {
            if (clear)
                resultRichTextBox.Clear();

            foreach (var item in Classes.ServiceRequest.Persons)
            {
                if (founded.HasValue && founded.Value && item.Founded)
                    resultRichTextBox.AppendText(item.ToString());
                else if (founded.HasValue && !founded.Value && !item.Founded)
                    resultRichTextBox.AppendText(item.ToString());
                else if (all.HasValue && all.Value)
                    resultRichTextBox.AppendText(item.ToString());
            }
        }

        private int NumberOfNotFoundCodes()
        {
            int notFound = 0;

            foreach (Classes.JuridicalPerson person in Classes.ServiceRequest.Persons)
            {
                if (!person.Founded)
                    notFound++;
            }

            return notFound;
        }

        #endregion Private Methods

        #region Event Handlers

        private void selectFileBtn_Click(object sender, EventArgs e)
        {
            openFileDialog.ShowDialog();

            fileNameTextBox.Text = openFileDialog.FileName;            
        }

        private void requestBtn_Click(object sender, EventArgs e)
        {
            resultFilterComboBox.Enabled = false;
            requestBtn.Enabled = false;

            Classes.ServiceRequest.Persons.Clear();

            StartRequestInNewThread(); 
           
            AppendTo(true, null, true); // Show All
            notFoundCodes.Text = NumberOfNotFoundCodes().ToString();

            resultFilterComboBox.Enabled = true;
            requestBtn.Enabled = true;
        }

        private void searchBtn_Click(object sender, EventArgs e)
        {   
            int startindex = 0;
            
            if (findText.Text.Length > 0)
                startindex = FindMyText(findText.Text.Trim(), start, resultRichTextBox.Text.Length);

            if (startindex >= 0)
            {
                resultRichTextBox.SelectionColor = Color.Red;                
               
                int endindex = findText.Text.Length;
               
                resultRichTextBox.Select(startindex, endindex);
     
                start = startindex + endindex;

                resultRichTextBox.ScrollToCaret();
            }
        }        

        private void findText_TextChanged(object sender, EventArgs e)
        {
            start = 0;
            indexOfSearchText = 0;
        }

        private void resultFilterComboBox_SelectedIndexChanged(object sender, EventArgs e)
        {
            switch (resultFilterComboBox.SelectedIndex)
            {
                case (int)SearchResultState.All: AppendTo(true, null, true); break;
                case (int)SearchResultState.Found: AppendTo(null, true, true); break;
                case (int)SearchResultState.NotFound: AppendTo(null, false, true); break;
            }
        }        

        #endregion Events                

        private void pictureBox1_Click(object sender, EventArgs e)
        {
            AboutBox about = new AboutBox();
            about.ShowDialog();
        }
    }
}
